package com.cms.service;

import com.cms.dao.SysResourceDao;
import com.cms.dao.SysRoleResourceDao;
import com.cms.dao.SysUserRoleDao;
import com.cms.model.bo.BussinessMsg;
import com.cms.model.bo.Tree;
import com.cms.model.dto.ResourceChildrenMenuDto;
import com.cms.model.dto.ResourceMenuDto;
import com.cms.model.vo.SysResource;
import com.cms.utils.constant.BusinessConstants;
import com.cms.utils.constant.BussinessCode;
import com.cms.utils.tools.BussinessMsgUtil;
import com.cms.utils.tools.KeyConfig;
import com.github.pagehelper.PageHelper;

import org.apache.commons.lang.StringUtils;
import org.nutz.json.Json;
import org.nutz.json.JsonFormat;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

/**菜单资源服务类*/
@Service
public class SysResourceService extends BaseService<SysResource>{
	
	@Autowired
	private SysUserRoleDao userRoleDao;
	
	@Autowired
	private SysResourceDao resourceDao;
	
	@Autowired
	private SysRoleResourceDao roleResourceDao;
	
	@Autowired
	private ShiroService shiroService;

    /**
     * 资源信息分页显示
     * @param resource
     * @return
     */
    public String selectResourceResultPageList(SysResource resource){
    	PageHelper.startPage(resource.getPage(),resource.getLimit());
    	return setPage(resourceDao.selectResourceList(resource));
    }

    /**
     * 顶部菜单展示封装
     * @return
     */
    public String selectResMenuTop(Integer currentLoginId){
    	List<Integer> roleIdList = userRoleDao.selectUserRoleByUserId(currentLoginId);
    	Integer[] roleIds = roleIdList.toArray(new Integer[roleIdList.size()]);
        List<ResourceMenuDto> parentResList =  resourceDao.selectParentIdResList(roleIds);
        if(null != parentResList && !parentResList.isEmpty()){
            return Json.toJson(parentResList, JsonFormat.full());
        }
        return null;
    }

    /**
     * 根据父级菜单Id查询各级菜单信息
     * @param resParentid 父级菜单
     * @return
     */
    public  String selectResLevelListByParentid(Integer currentLoginId,Integer resParentId) {
    	List<Integer> roleIdList = userRoleDao.selectUserRoleByUserId(currentLoginId);
    	Integer[] roleIds = roleIdList.toArray(new Integer[roleIdList.size()]);
        //二级菜单
        List<SysResource> ResLevel2List = resourceDao.selectResLevelListByParentId(roleIds,resParentId);
        if(null != ResLevel2List && !ResLevel2List.isEmpty()){
            List<ResourceMenuDto> resourceMenu = new ArrayList<>();
            for (SysResource resource2 : ResLevel2List) {
                ResourceMenuDto menuDto = new ResourceMenuDto();
                menuDto.setTitle(resource2.getResName());
                menuDto.setIcon(resource2.getResImage());
                menuDto.setHref(resource2.getResLinkAddress());
                //三级菜单
                List<SysResource> ResLevel3List =resourceDao.selectResLevelListByParentId(roleIds,resource2.getResId());
                if(null != ResLevel3List && !ResLevel3List.isEmpty()) {
                    List<ResourceChildrenMenuDto> childrens = new ArrayList<>();
                    for (SysResource resource3 : ResLevel3List) {
                        ResourceChildrenMenuDto children = new ResourceChildrenMenuDto();
                        children.setTitle(resource3.getResName());
                        children.setIcon(resource3.getResImage());
                        children.setHref(resource3.getResLinkAddress());
                        childrens.add(children);
                    }
                    menuDto.setChildren(childrens);
                }
                resourceMenu.add(menuDto);
            }
            return Json.toJson(resourceMenu, JsonFormat.full());
        }
        return null;
    }


    /**
     * 查询所有资源信息用以角色赋权限的时候Tree菜单显示
     */
    public List<Tree> selectResourceAllTree() {
        // 菜单资源集合
        List<SysResource> resList = resourceDao.selectResourceAllList();
        // tree 树形集合
        List<Tree> trees = new ArrayList<Tree>();
        if (null != resList && !resList.isEmpty()) {
            for (SysResource r : resList) {
                Tree tree = new Tree();
                tree.setId(r.getResId());
                if (null != r.getResParentId()) {
                    tree.setPid(r.getResParentId());
                }
                tree.setText(r.getResName());
                tree.setIconCls(r.getResImage());
                Map<String, Object> attr = new HashMap<String, Object>();
                attr.put("url", r.getResLinkAddress());
                tree.setAttributes(attr);
                trees.add(tree);
            }
        }
        return trees;
    }

    /**
     * 根据菜单类型和菜单级别查询菜单信息
     * @param resType
     * @param resLevel
     * @param resId 菜单Id
     * @return
     */
    public List<SysResource> selectParentResListByResTypeAndResLevel(Integer resType,Integer resLevel,Integer resId){
        //1.菜单类型为0-菜单，菜单级别为1级菜单 父级菜单为空
        if(BusinessConstants.SYS_RES_TYPE_0.getCode().equals(resType) && BusinessConstants.SYS_RES_LEVEL_1.getCode().equals(resLevel)){
            return null;
        }
        //2.菜单类型为0-菜单，菜单级别为2级菜单 查询1级父级菜单
        if(BusinessConstants.SYS_RES_TYPE_0.getCode().equals(resType) && BusinessConstants.SYS_RES_LEVEL_2.getCode().equals(resLevel)){
            return  resourceDao.selectParentResListByResTypeAndResLevel(BusinessConstants.SYS_RES_TYPE_0.getCode(),BusinessConstants.SYS_RES_LEVEL_1.getCode(),resId);
        }
        //3.菜单类型为0-菜单，菜单级别为3级菜单 查询2级父级菜单
        if(BusinessConstants.SYS_RES_TYPE_0.getCode().equals(resType) && BusinessConstants.SYS_RES_LEVEL_3.getCode().equals(resLevel)){
            return  resourceDao.selectParentResListByResTypeAndResLevel(BusinessConstants.SYS_RES_TYPE_0.getCode(),BusinessConstants.SYS_RES_LEVEL_2.getCode(),resId);
        }
        //4.菜单类型为1-按钮，菜单级别为3级菜单 查询3级菜单
        if(BusinessConstants.SYS_RES_TYPE_1.getCode().equals(resType) && BusinessConstants.SYS_RES_LEVEL_3.getCode().equals(resLevel)){
            return  resourceDao.selectParentResListByResTypeAndResLevel(BusinessConstants.SYS_RES_TYPE_0.getCode(),BusinessConstants.SYS_RES_LEVEL_3.getCode(),resId);
        }
        return null;
    }



    /**
     * 新增或者修改资源信息
     * @param res 资源对象
     * @param loginName 当前登录用户
     * @return
     * @throws Exception
     */
    @Transactional
    public BussinessMsg saveOrUpdateResource(SysResource res,String loginName) throws Exception{
        logger.info("保存菜单信息开始");
        long start = System.currentTimeMillis();
        try {
            //保存菜单资源信息
            if (null == res.getResId()) {
                res.setResModelCode(KeyConfig.randomResourceModeCode());
                res.setCreator(loginName);
                res.setCreateTime(new Date());
                resourceDao.insertSelective(res);
            } else {
                //更新菜单资源信息
                res.setModifier(loginName);
                res.setModifyTime(new Date());
                resourceDao.updateByPrimaryKeySelective(res);
            }
        } catch (Exception e) {
            logger.error("保存菜单信息方法内部错误",e);
            throw e;
        }finally {
            logger.info("保存菜单信息结束,用时" + (System.currentTimeMillis() - start) + "毫秒");
        }
        return BussinessMsgUtil.returnCodeMessage(BussinessCode.GLOBAL_SUCCESS);
    }

    /**
     * 查询有效的,URL不为空的所有菜单信息
     * @return
     */
    public List<SysResource>selectResUrlAllList(){
        return resourceDao.selectResUrlAllList();
    }

    /**
     * 根据用户Id查询用户资源菜单信息
     * @param userId 用户Id
     * @return
     */
    public List<SysResource>selectResListByUserId(Integer userId){
        return resourceDao.selectResListByUserId(userId);
    }

	public List<SysResource> selectResourceAllList() {
		return resourceDao.selectResourceAllList();
	}

	public Long selectCountResParentByResId(Integer resId) {
		return resourceDao.selectCountResParentByResId(resId);
	}

	 /**
     * 菜单状态失效
     * @param resId	菜单Id
     * @param loginName 当前登录用户名
     * @return
     * @throws Exception
     */
    @Transactional
    public BussinessMsg updateMenuStatus(Integer resId,String loginName) throws Exception{
        logger.info("菜单失效开始,当前菜单Id:"+resId);
        long start = System.currentTimeMillis();
        try {
        	List<String> totleList = new ArrayList<String>();
        	totleList.add(String.valueOf(resId));
        	List<String> ylist = resourceDao.selectSubIdByResId(String.valueOf(resId));
        	totleList.addAll(ylist);
        	if(ylist!=null&&ylist.size()>0){
        		List<String> elist = resourceDao.selectSubIdByResId(StringUtils.join(ylist, ","));
        		totleList.addAll(elist);
        		if(elist!=null&&elist.size()>0){
        			List<String> slist = resourceDao.selectSubIdByResId(StringUtils.join(elist, ","));//三级菜单
        			totleList.addAll(slist);
        		}
        	}
        	String totleResId = StringUtils.join(totleList, ",");
            //解除角色与菜单绑定关系
            roleResourceDao.deleteRoleResourceByResId(totleResId);

            //更改菜单状态为1-失效
            Map<String, Object> params = new HashMap<String, Object>();
            params.put("resStatus", BusinessConstants.SYS_STATUS_1.getCode());
            params.put("modifier", loginName);
            params.put("modifierTime", new Date());
            params.put("resIds", totleList.toArray());
            resourceDao.updateMenuByStatus(params);
            //清空用户权限缓存信息
            shiroService.clearAllCacheAuth();
        } catch (Exception e) {
            logger.error("菜单失效方法内部错误",e);
            throw e;
        }finally {
        	logger.info("菜单失效结束,用时" + (System.currentTimeMillis() - start) + "毫秒");
        }
        return BussinessMsgUtil.returnCodeMessage(BussinessCode.GLOBAL_SUCCESS);
    }
}
